package com.balance.anole.business.service;

import java.util.Date;
import java.util.List;
import java.util.Map;
import java.util.Set;

import com.balance.anole.admin.to.AgentTO;
import com.balance.anole.admin.to.StaffInfoTO;
import com.balance.anole.admin.to.WarehouseTO;
import com.balance.anole.business.to.BusinessDateTO;
import com.balance.anole.business.to.OrderTO;
import com.balance.anole.business.to.OrderTrackingTO;
import com.balance.anole.business.to.ProductBrandTO;
import com.balance.anole.business.to.ProductColorTO;
import com.balance.anole.business.to.ProductGroupTO;
import com.balance.anole.business.to.ProductItemTO;
import com.balance.anole.business.to.ProductPictureTO;
import com.balance.anole.business.to.ProductPriceTO;
import com.balance.anole.business.to.ProductSizeTO;
import com.balance.anole.business.to.ProductStockCheckDetailTO;
import com.balance.anole.business.to.ProductStockCheckTO;
import com.balance.anole.business.to.ProductStockTO;
import com.balance.anole.business.to.ProductTO;
import com.balance.anole.business.to.WarehouseInTO;
import com.balance.anole.business.to.WarehouseOutTO;
import com.balance.anole.business.vo.OrderSummaryVO;
import com.balance.anole.business.vo.ProductItemSearchTO;
import com.balance.anole.business.vo.ProductSearchTO;

public interface BusinessService {


	/*======================== Order Manage ========================*/
	public OrderTO getOrder(Integer id);

	/**
	 *
	 * @param staffId
	 * @param txnTms
	 * @return OrderTO
	 */
	public OrderTO getOrder(String staffId, Date txnTms);

	/**
	 * Save new order with details. New txs id is generated and set back to
	 * TO for UI display.
	 * Update order if the order exists.
	 * Fulfill fields which are need calculation for UI display.
	 *
	 * @param order
	 * @return OrderTO
	 */
	public OrderTO saveOrUpdateOrder(OrderTO order);

	/**
	 * Get all orders created by the given staff.
	 *
	 * @param creater
	 * @return List<OrderSummaryVO>
	 */
	public List<OrderSummaryVO> getOrdersByStaff(StaffInfoTO creater);

	/**
	 * Get all orders created by the given staff.
	 *
	 * @param creater
	 * @return List<OrderSummaryVO>
	 */
	public List<OrderSummaryVO> getOrders4VerifyByStaff(StaffInfoTO verifier);

	/**
	 * Get all orders created by the given staff.
	 *
	 * @param creater
	 * @return List<OrderSummaryVO>
	 */
	public List<OrderSummaryVO> getAllOrders4Verify();

	/**
	 * Get all orders which txs Id contains the given txsId.
	 *
	 * @param txsId
	 * @return List<OrderTO>
	 */
	public List<OrderTO> getOrdersByTxsId(String txsId);

	/**
	 * Delete order
	 * @param order
	 */
	public void deleteOrder(OrderTO order);

	/**
	 * @param order
	 */
	public void commitOrder(OrderTO order);

	/**
	 * @param order
	 */
	public void verify(OrderTO order);

	/**
	 * @param order
	 */
	public void reject(OrderTO order);

	/**
	 * Generate a list of product items which are top N of them.
	 * @return
	 */
	@SuppressWarnings("unchecked")
	public List orderProductItemTop(Date from,Date to);

	/**
	 * Generate a new transaction id. The id should be globally unique.
	 * @return
	 */
	public String generateNewTxnId();

	/**
	 * @param txnId
	 */
	public void deleteOrder(String txnId);

	/**
	 * @param txnId
	 */
	public void commitOrder(String txnId);

	/**
	 * @param txnId
	 */
	public void verify(String txnId);

	/**
	 * @param txnId
	 */
	public void reject(String txnId);

	/*======================== Product Manage ========================*/

	/**
	 * Insert produceTO.
	 *
	 * @param produceTO
	 * @return null
	 */
	public void insertOrupdateProductTO(ProductTO productTO);

	/**
	 * Create product item.
	 *
	 * @param productItemTO
	 * @return null
	 */
	public void insertOrUpdateProductItemTO(ProductItemTO productItemTO);

	/**
	 * insert ProductGroupTO
	 *
	 * @param productGroupTO
	 * @return null
	 */
	public void insertOrUpdateProductGroupTO(ProductGroupTO productGroupTO);
	
	
	public void insertOrUpdateProductStockTO(ProductStockTO productStockTO);

	/**
	 * Get a list of products by given search conditions. If the condition field
	 * is empty, the condition is ignored. The logical relationship between the conditions
	 * is AND.
	 *
	 * @param searchTO
	 * @return
	 */
	public List<ProductTO> getProducts(ProductSearchTO searchTO);

	/**
	 * Get a list of product items by given search conditions. If the condition field
	 * is empty, the condition is ignored. The logical relationship between the conditions
	 * is AND.
	 *
	 * @param ProductItemSearchTO
	 * @return List<ProductItemTO>
	 */
	public List<ProductItemTO> getProductItems(ProductItemSearchTO searchTO);

	/**
	 * Get product using product id. Should only return one record since product id
	 * is the primary key.
	 *
	 * @param productId
	 * @return ProductTO
	 */
	public ProductTO getProductTOByProductId(String productId);

	/**
	 * Delete product by ids.
	 * @param ids
	 * @return null
	 */
	public void deleteProductByIds(Integer[] ids);

	/**
	 * Get product by id.
	 * @param id
	 * @return ProductTO
	 */
	public ProductTO getProductTO(Integer id);

	/**
	 * Get product item using item id. Should only return one record since item id
	 * is the primary key.
	 *
	 * @param itemId
	 * @return ProductItemTO
	 */
	public ProductItemTO getProductItemTOByItemId(String itemId);

	public List<ProductItemTO> getProductItemListByPrdId(Integer prdId);

	public boolean isExistsPrdSizeColor(int prdId, int sizeId, int colorId);

	public Object[] importProduct(StaffInfoTO curUser, List dataList);

	public int getNextPrdSN(String preSn);



	/*======================== ProductGroup Manage ========================*/

	/**
	 * Get a list of productGroups by given productType. If the condition field
	 * is empty, the condition is ignored.
	 *
	 * @param productType
	 * @return
	 */
	public List<ProductGroupTO> getProductGroupsByProductType(String productType);

	/**
	 * Get a ProductGroupTO by id
	 *
	 * @param id
	 * @return ProductGroupTO
	 */
	public ProductGroupTO getProductGroupTO(Integer id);


	/*======================== ProductBrand Manage ========================*/

	/**
	 * Insert or update productBrandTO
	 * @param productBrandTO
	 * @return NULL
	 */
	public void insertOrUpdateProductBrandTO(ProductBrandTO productBrandTO);

	/**
	 * Get productBrand by id.
	 * @param id
	 * @return ProductBrandTO
	 */
	public ProductBrandTO getProductBrandTO(Integer id);


	/*======================== ProductColor Manage ========================*/

	/**Insert ProductColor into database
	 * @param ProductColorTO
	 * @return NULL
	 */
	public void insertOrUpdateProductColorTO(ProductColorTO productColorTO);

	/**
	 * @param id
	 * @return
	 */
	public ProductColorTO getProductColorTO(Integer id);

	/**
	 * get product color list
	 * @param paramMap
	 * @return
	 */
	public List<ProductColorTO> getProductColorList(Map<String,Object> paramMap);


	/*======================== ProductSize Manage ========================*/

	/**
	 * Insert ProductSize into database
	 * @param ProductSizeTO
	 * @return NULL
	 */
	public void insertOrUpdateProductSizeTO(ProductSizeTO productSizeTO);

	/**
	 * @param id
	 * @return
	 */
	public ProductSizeTO getProductSizeTO(Integer id);

	/**
	 * get product size list
	 * @param paramMap
	 * @return
	 */
	public List<ProductSizeTO> getProductSizeList(Map<String,Object> paramMap);

	/*======================== ProductPictureTO Manage ========================*/
	public void insertOrUpdatePictureTO(ProductPictureTO productPictureTO);

	/**
	 * @param productTO
	 * @return
	 */
	public List<ProductPictureTO> getProductPictureTOs(ProductTO productTO);

	/**
	 * @param id
	 * @return
	 */
	public ProductPictureTO getProductPictureTO(Integer id);

	/**
	 * Delete product pic by ids.
	 * @param ids
	 */
	public void deleteProductPicByIds(Integer[] ids);

	/*======================== BusinessDate Manage ========================*/
	/**Insert BusinessDateTO into database
	 * @param BusinessDateTO
	 * @return null
	 */
	public void insertNewBusinessDate(BusinessDateTO businessDate);

	/*======================== ProductItem manage ========================*/
	public ProductItemTO getProductItem(Integer id);


	/*======================== ProductPrice manage ========================*/
	public ProductPriceTO getProductPrice(Integer id);


	public ProductPriceTO getProductPrice(Integer prdId, String priceType);

	public AgentTO getAgent(Integer id);
	
	/*======================== ProductStock manage ========================*/
	/**
	 * @param id
	 * @return ProductStockTO
	 */
	public ProductStockTO getProductStock(Integer id);
	
	public void insertOrUpdateProductStockCheck(ProductStockCheckTO productStockCheck);
	
	public ProductStockCheckTO getProductStockCheckTO(Integer id);
		
	public void saveOrUpdateProductStock(ProductStockTO productStockTO);
	
	public List getProductStockCheckDetailList(Integer prdStockCheckId);
	
	public void saveAndUpdateProductStockCheckDetail(ProductStockCheckDetailTO productStockCheckDetail);
	
	public List<ProductStockTO> getProductStockTOByAgentIdAndItemId(Map<String,Object> paramMap);

	/*======================== Order Manage ========================*/
	/**get OrderTracting list
	 * @param orderId
	 * @return List
	 */
	public List<OrderTrackingTO> listOrderTracking(Integer orderId);

	public OrderTrackingTO getLastOrderTracking(Integer orderId);

	public BusinessDateTO getCurrentBusinessDate();

	public Set<Date> getUploadFailedBusinessDates(AgentTO agent);
	
	/*======================== warehouse Manage ========================*/
	
	public WarehouseTO getWarehouseTO(Integer id);
	
	/*======================== outwarehouse Manage ========================*/
	public WarehouseOutTO getWarehouseOutTO(Integer id);
	
	public void saveOrUpdateWarehouseOutTO(WarehouseOutTO to);
	
	public List<WarehouseOutTO> getWarehouseOutTOByOrderId(Integer orderId);
	
	/*======================== inwarehouse Manage ========================*/
	public WarehouseInTO getWarehouseInTO(Integer id);
	
	public void saveOrUpdateWarehouseInTO(WarehouseInTO to);
	
	public List<WarehouseInTO> getWarehouseInTOByOrderId(Integer orderId);
}
